package com.kurt.controller;

import com.kurt.annotation.Log;
import com.kurt.common.PageResult;
import com.kurt.common.Result;
import com.kurt.dto.UserDTO;
import com.kurt.dto.create.UserCreateRequest;
import com.kurt.dto.query.UserQueryRequest;
import com.kurt.dto.update.UserUpdateRequest;
import com.kurt.service.UserService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.domain.Page;
import org.springframework.web.bind.annotation.*;

import java.util.List;


/**
 * 用户控制器
 * 处理用户相关的HTTP请求
 */
@Slf4j
@RestController
@RequestMapping("/users")
@RequiredArgsConstructor
public class UserController extends BaseController {

    private final UserService userService;

    /**
     * 创建用户
     *
     * @param createRequest 创建请求
     * @return 用户信息
     */
    @Log(title = "创建用户", businessType = 1)
    @PostMapping
    public Result<UserDTO> createUser(@RequestBody UserCreateRequest createRequest) {
        try {
            createRequest.setLoginUserId(getCurrentUserId());
            createRequest.setCreateUserId(getCurrentUserId());
            log.info("创建用户请求: {}", createRequest.getAccount());
            UserDTO user = userService.createUser(createRequest);
            return Result.success("用户创建成功", user);
        } catch (Exception e) {
            log.error("创建用户失败: {}", e.getMessage(), e);
            return Result.error("创建用户失败: " + e.getMessage());
        }
    }

    /**
     * 更新用户
     *
     * @param updateRequest 更新请求
     * @return 用户信息
     */
    @Log(title = "更新用户", businessType = 2)
    @PutMapping
    public Result<UserDTO> updateUser(@RequestBody UserUpdateRequest updateRequest) {
        try {
            updateRequest.setLoginUserId(getCurrentUserId());
            updateRequest.setUpdateUserId(getCurrentUserId());
            log.info("更新用户请求: {}", updateRequest.getId());
            UserDTO user = userService.updateUser(updateRequest);
            return Result.success("用户更新成功", user);
        } catch (Exception e) {
            log.error("更新用户失败: {}", e.getMessage(), e);
            return Result.error("更新用户失败: " + e.getMessage());
        }
    }

    /**
     * 根据ID获取用户详情
     *
     * @param id 用户ID
     * @return 用户信息
     */
    @GetMapping("/{id}")
    public Result<UserDTO> getUserById(@PathVariable("id") Long id) {
        try {
            log.info("获取用户详情请求: {}", id);
            UserDTO user = userService.getUserById(id);
            return Result.success("获取用户详情成功", user);
        } catch (Exception e) {
            log.error("获取用户详情失败: {}", e.getMessage(), e);
            return Result.error("获取用户详情失败: " + e.getMessage());
        }
    }

    /**
     * 分页查询用户
     *
     * @param queryRequest 查询请求
     * @return 分页结果
     */
    @PostMapping("/page")
    public Result<PageResult<UserDTO>> getUserPage(@RequestBody UserQueryRequest queryRequest) {
        try {
            queryRequest.setLoginUserId(getCurrentUserId());
            log.info("分页查询用户请求: {}", queryRequest);
            Page<UserDTO> userPage = userService.getUserPage(queryRequest);

            // 转换为PageResult
            PageResult<UserDTO> pageResult = PageResult.of(
                    queryRequest.getPageNum(),
                    queryRequest.getPageSize(),
                    userPage.getTotalElements(),
                    userPage.getContent()
            );

            return Result.success("分页查询用户成功", pageResult);
        } catch (Exception e) {
            log.error("分页查询用户失败: {}", e.getMessage(), e);
            return Result.error("分页查询用户失败: " + e.getMessage());
        }
    }

    /**
     * 查询用户列表
     *
     * @param queryRequest 查询请求
     * @return 用户列表
     */
    @PostMapping("/list")
    public Result<List<UserDTO>> getUserList(@RequestBody UserQueryRequest queryRequest) {
        try {
            queryRequest.setLoginUserId(getCurrentUserId());
            log.info("查询用户列表请求: {}", queryRequest);
            List<UserDTO> users = userService.getUserList(queryRequest);
            return Result.success("查询用户列表成功", users);
        } catch (Exception e) {
            log.error("查询用户列表失败: {}", e.getMessage(), e);
            return Result.error("查询用户列表失败: " + e.getMessage());
        }
    }

    /**
     * 删除用户
     *
     * @param id 用户ID
     * @return 删除结果
     */
    @Log(title = "删除用户", businessType = 3)
    @DeleteMapping("/{id}")
    public Result<Boolean> deleteUser(@PathVariable("id") Long id) {
        try {
            log.info("删除用户请求: {}", id);
            boolean success = userService.deleteUser(id);
            return Result.success("用户删除成功", success);
        } catch (Exception e) {
            log.error("删除用户失败: {}", e.getMessage(), e);
            return Result.error("删除用户失败: " + e.getMessage());
        }
    }

    /**
     * 批量删除用户
     *
     * @param ids 用户ID列表
     * @return 删除结果
     */
    @Log(title = "批量删除用户", businessType = 3)
    @DeleteMapping("/batch")
    public Result<Boolean> deleteUsers(@RequestBody List<Long> ids) {
        try {
            log.info("批量删除用户请求: {}", ids);
            boolean success = userService.deleteUsers(ids);
            return Result.success("批量删除用户成功", success);
        } catch (Exception e) {
            log.error("批量删除用户失败: {}", e.getMessage(), e);
            return Result.error("批量删除用户失败: " + e.getMessage());
        }
    }

    /**
     * 管理员重置用户密码
     *
     * @param id          用户ID
     * @param newPassword 新密码
     * @return 重置结果
     */
    @Log(title = "管理员重置用户密码", businessType = 2)
    @PostMapping("/{id}/reset-password")
    public Result<Boolean> resetPassword(@PathVariable("id") Long id, @RequestParam String newPassword) {
        try {
            log.info("重置用户密码请求: {}", id);
            boolean success = userService.resetPassword(id, newPassword);
            return Result.success("密码重置成功", success);
        } catch (Exception e) {
            log.error("重置用户密码失败: {}", e.getMessage(), e);
            return Result.error("重置用户密码失败: " + e.getMessage());
        }
    }

    /**
     * 用户修改密码
     *
     * @param id          用户ID
     * @param oldPassword 旧密码
     * @param newPassword 新密码
     * @return 修改结果
     */
    @Log(title = "用户修改密码", businessType = 2)
    @PostMapping("/{id}/change-password")
    public Result<Boolean> changePassword(@PathVariable("id") Long id,
                                          @RequestParam String oldPassword,
                                          @RequestParam String newPassword) {
        try {
            log.info("修改用户密码请求: {}", id);
            boolean success = userService.changePassword(id, oldPassword, newPassword);
            return Result.success("密码修改成功", success);
        } catch (Exception e) {
            log.error("修改用户密码失败: {}", e.getMessage(), e);
            return Result.error("修改用户密码失败: " + e.getMessage());
        }
    }

    /**
     * 分配用户角色
     *
     * @param userId  用户ID
     * @param roleIds 角色ID列表
     * @return 分配结果
     */
    @PostMapping("/{userId}/roles")
    public Result<Boolean> assignRoles(@PathVariable("userId") Long userId, @RequestBody List<Long> roleIds) {
        try {
            log.info("分配用户角色请求: userId={}, roleIds={}", userId, roleIds);
            boolean success = userService.assignRoles(userId, roleIds);
            return Result.success("角色分配成功", success);
        } catch (Exception e) {
            log.error("分配用户角色失败: {}", e.getMessage(), e);
            return Result.error("分配用户角色失败: " + e.getMessage());
        }
    }

    /**
     * 获取用户角色列表
     *
     * @param userId 用户ID
     * @return 角色列表
     */
    @GetMapping("/{userId}/roles")
    public Result<List<UserDTO.RoleDTO>> getUserRoles(@PathVariable("userId") Long userId) {
        try {
            log.info("获取用户角色列表请求: {}", userId);
            List<UserDTO.RoleDTO> roles = userService.getUserRoles(userId);
            return Result.success("获取用户角色列表成功", roles);
        } catch (Exception e) {
            log.error("获取用户角色列表失败: {}", e.getMessage(), e);
            return Result.error("获取用户角色列表失败: " + e.getMessage());
        }
    }

    /**
     * 获取用菜单户权限列表
     *
     * @param userId 用户ID
     * @return 权限列表
     */
    @GetMapping("/{userId}/permissions")
    public Result<List<String>> getUserPermissions(@PathVariable("userId") Long userId) {
        try {
            log.info("获取用户权限列表请求: {}", userId);
            List<String> permissions = userService.getUserPermissions(userId);
            return Result.success("获取用户权限列表成功", permissions);
        } catch (Exception e) {
            log.error("获取用户权限列表失败: {}", e.getMessage(), e);
            return Result.error("获取用户权限列表失败: " + e.getMessage());
        }
    }

    /**
     * 根据组织ID获取用户列表
     *
     * @param organizationId 组织ID
     * @return 用户列表
     */
    @GetMapping("/organization/{organizationId}")
    public Result<List<UserDTO>> getUsersByOrganizationId(@PathVariable("organizationId") Long organizationId) {
        try {
            log.info("根据组织ID获取用户列表请求: {}", organizationId);
            List<UserDTO> users = userService.getUsersByOrganizationId(organizationId, getCurrentUserId());
            return Result.success("获取用户列表成功", users);
        } catch (Exception e) {
            log.error("根据组织ID获取用户列表失败: {}", e.getMessage(), e);
            return Result.error("获取用户列表失败: " + e.getMessage());
        }
    }

    /**
     * 根据角色ID获取用户列表
     *
     * @param roleId 角色ID
     * @return 用户列表
     */
    @GetMapping("/role/{roleId}")
    public Result<List<UserDTO>> getUsersByRoleId(@PathVariable("roleId") Long roleId) {
        try {
            log.info("根据角色ID获取用户列表请求: {}", roleId);
            List<UserDTO> users = userService.getUsersByRoleId(roleId, getCurrentUserId());
            return Result.success("获取用户列表成功", users);
        } catch (Exception e) {
            log.error("根据角色ID获取用户列表失败: {}", e.getMessage(), e);
            return Result.error("获取用户列表失败: " + e.getMessage());
        }
    }

    /**
     * 检查账号是否存在
     *
     * @param account 账号
     * @return 是否存在
     */
    @GetMapping("/exists/account/{account}")
    public Result<Boolean> existsByAccount(@PathVariable("account") String account) {
        try {
            log.info("检查账号是否存在请求: {}", account);
            boolean exists = userService.existsByAccount(account);
            return Result.success("检查账号是否存在成功", exists);
        } catch (Exception e) {
            log.error("检查账号是否存在失败: {}", e.getMessage(), e);
            return Result.error("检查账号是否存在失败: " + e.getMessage());
        }
    }

    /**
     * 检查手机号是否存在
     *
     * @param phone 手机号
     * @return 是否存在
     */
    @GetMapping("/exists/phone/{phone}")
    public Result<Boolean> existsByPhone(@PathVariable("phone") String phone) {
        try {
            log.info("检查手机号是否存在请求: {}", phone);
            boolean exists = userService.existsByPhone(phone);
            return Result.success("检查手机号是否存在成功", exists);
        } catch (Exception e) {
            log.error("检查手机号是否存在失败: {}", e.getMessage(), e);
            return Result.error("检查手机号是否存在失败: " + e.getMessage());
        }
    }
}
